package com.example.demo.aop;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
import org.springframework.util.StopWatch;

/**
 * Creat with IntelliJ IDEA
 * Description:
 * User:WZW
 * Date:2022-08-25
 * Time:20:51
 */
@Aspect //表明此类为一个切面
@Component
public class UserAspect {
    // 定义一个切点（设置拦截规则）
    @Pointcut("execution(* com.example.demo.controller.UserController.*(..))")
    public void pointcut() {

    }

    // 定义pointcut切点的前置通知
    @Before("pointcut()")
    public void doBefore() {
        System.out.println("前置通知");
    }

    @After("pointcut()")
    public void doAfter() {
        System.out.println("后置通知");
    }

    @AfterReturning("pointcut()")
    public void doAfterReturning() {
        System.out.println("AfterReturning");
    }

    @AfterThrowing("pointcut()")
    public void doAfterThrowing() {
        System.out.println("AfterThrowing");
    }

    // 针对 pointcut 切点的环绕通知
    @Around("pointcut()")
    public Object doAround(ProceedingJoinPoint joinPoint) {
        Object result = null;
        // spring 中的时间统计对象
        StopWatch stopWatch = new StopWatch();
//        System.out.println("Around 方法开始执行");
        Long start = System.currentTimeMillis();
        try {
            stopWatch.start();//开始计时
            // 执行目标方法以及目标方法相应的通知
            result = joinPoint.proceed();
            stopWatch.stop();//停止计时
        } catch (Throwable e) {
            e.printStackTrace();
        }
//        Long end = System.currentTimeMillis();
//        System.out.println(end - start);
        System.out.println(joinPoint.getSignature().getDeclaringTypeName()
                + "." + joinPoint.getSignature().getName()
                + "执行花费的时间" + stopWatch.getTotalTimeMillis() + "ms");
        System.out.println("Around 方法结束执行");
        return result;
    }

}
